//
//  Codable+.swift
//  HoneyChat
//
//  Created by hccc on 2023/3/17.
//

import Foundation

extension Encodable {
    func toJSON() -> [String: Any]? {
        do {
            let data = try JSONEncoder().encode(self)
            let json = try JSONSerialization.jsonObject(with: data, options: .allowFragments) as? [String: Any]
            return json
        } catch {
            PPLog("有数据Encode失败啦")
            return nil
        }
    }

    func toCodableString(prettyPrint: Bool = false) -> String? {
        if let anyObject = toJSON() {
            if JSONSerialization.isValidJSONObject(anyObject) {
                do {
                    let jsonData: Data
                    if prettyPrint {
                        jsonData = try JSONSerialization.data(withJSONObject: anyObject, options: [.prettyPrinted])
                    } else {
                        jsonData = try JSONSerialization.data(withJSONObject: anyObject, options: [])
                    }
                    return String(data: jsonData, encoding: .utf8)
                } catch {
                    PPLog("JSON转String失败")
                }
            } else {
                PPLog("JSON转String失败")
            }
        }
        return nil
    }
}

extension Array where Element: Encodable {
    func toJSONArray() -> [[String: Any]]? {
        compactMap { $0.toJSON() }
    }
}

extension Decodable {
    static func decode(from json: Any?) -> Self? {
        do {
            guard let json = json else { return nil }
            let data = try JSONSerialization.data(withJSONObject: json, options: .prettyPrinted)
            let model = try JSONDecoder().decode(Self.self, from: data)
            return model
        } catch {
            PPLog("有数据Decode失败啦")
            return nil
        }
    }
}

extension Array where Element: Decodable {
    static func decode(from array: [Any]?) -> [Element]? {
        guard let array = array else { return nil }
        return array.compactMap { e in
            Element.decode(from: e)
        }
    }
}
